import React, {
  forwardRef,
  useEffect,
  useImperativeHandle,
  useMemo,
  useRef,
  useState,
} from 'react';
import { CloudUploadOutlined } from '@ant-design/icons';
import { LoadingOutlined } from '@ant-design/icons';
import { InbizIcon, selectFilesByInput } from '@inbiz/utils';
import { message,Spin } from 'antd';
import { TextWidget, getMessage } from '@inbiz/react';
import { GetFolderInfoById } from '../services';

interface IProps {
  children?: React.ReactChildren;
  multiple?: boolean;
  directory?: boolean;
  disabled?: boolean;
  targetFolder?: { id: number; folderid: string | number }[];
  permission?: boolean;
  readOnly?: boolean;
  controlId?: string;
  title?: string;
  viewMode?:string;
  loading:boolean;
  onChange?: (value: any) => void;
}
interface IInputRef {
  value: any;
  click: () => void;
}

const UploadButton = forwardRef((props: IProps, ref) => {
  const {
    children,
    multiple = false,
    directory,
    disabled,
    targetFolder,
    permission,
    readOnly,
    controlId,
    viewMode,
    title,
    loading,
    onChange,
  } = props;
  const [showModal, setShowModal] = useState<boolean>(false);
  const inputRef = useRef<IInputRef>({
    value: '',
    click: () => {},
  });
  const uploadBtnRef = useRef<HTMLLabelElement>(null);
  const containerStyle: React.CSSProperties = {
    display: 'inline-block',
    position: 'relative',
    backgroundColor: readOnly ? '#f5f5f5' : '',
    cursor: readOnly ? 'no-drop' : '',
  };
  const inputStyle: React.CSSProperties = {
    bottom: 0,
    height: '32px',
    left: 0,
    margin: 0,
    opacity: 0,
    padding: 0,
    position: 'absolute',
    right: 0,
    top: 0,
    width: '100%',
    display: 'none',
  };
  const antIcon = <LoadingOutlined style={{ fontSize: 14 }} spin />;
  const fileChange = async (e: any, isFiles?: boolean) => {
    const files = isFiles ? e : e?.target.files;
    const res = await GetFolderInfoById({
      folderId: targetFolder![0]?.folderid,
    });
    if (res && res.data?.IsDeleted) {
      message.destroy();
      message.error(getMessage('inbizUpload.noFolder'));
      inputRef.current.value = '';
      return;
    }
    onChange && onChange(files);
    inputRef.current.value = '';
  };
  const handleClick = async (e: any) => {
    if (disabled) {
      return;
    }
    if (!(targetFolder && targetFolder?.length > 0) && !disabled) {
      message.destroy();
      message.error(getMessage('inbizUpload.noSetFolder'));
      return;
    } else if (!permission && !disabled) {
      message.destroy();
      message.error(getMessage('inbizUpload.noPermission'));
      return;
    }
    if (multiple && directory) {
      setShowModal(true);
      return;
    }
    inputRef.current.click();
  };
  const changeModalStatus = (e: any) => {
    const className = e.target.getAttribute('class');
    if (
      className !== 'react-fine-uploader-file-input-modal' &&
      className !==
        `react-fine-uploader-file-input-container react-fine-uploader-gallery-file-input-container ${controlId}`
    ) {
      setShowModal(false);
    }
  };
  const renderContent = useMemo(() => {
    return (
      children || (
        <span>
          <CloudUploadOutlined className="react-fine-uploader-gallery-file-input-upload-icon" />
          {title}
          <Spin indicator={antIcon} spinning={loading} style={{marginLeft:'10px'}}/>
        </span>
      )
    );
  }, [children, title,loading]);
  const renderModal = useMemo(() => {
    return showModal ? (
      <div className="react-fine-uploader-file-input-modal">
        <div
          className="react-fine-uploader-file-input-modal-btn-titile"
          onClick={(e) => {
            e && e.stopPropagation();
            setShowModal(false);
            selectFilesByInput({
              type: 'file',
              multiple: multiple,
              success(files: File[]) {
                fileChange(files, true)
              },
            });
          }}
        >
          <InbizIcon
            type="icon-shangchuanwenjian"
            style={{ fontSize: '16px', marginRight: '8px' }}
          />
          <TextWidget>inbizUpload.uploadFile</TextWidget>
        </div>
        <div
          className="react-fine-uploader-file-input-modal-btn-titile"
          onClick={(e) => {
            e && e.stopPropagation();
            setShowModal(false);
            selectFilesByInput({
              type: 'folder',
              multiple: multiple,
              success(files: File[]) {
                fileChange(files, true);
              },
            });
          }}
        >
          <InbizIcon
            type="icon-shangchuanwenjianjia"
            style={{ fontSize: '16px', marginRight: '8px' }}
          />
          <TextWidget>inbizUpload.uploadFolder</TextWidget>
        </div>
      </div>
    ) : null;
  }, [showModal, multiple]);

  useImperativeHandle(
    ref,
    () => ({
      click: () => {
        return uploadBtnRef.current?.click();
      },
    }),
    [],
  );

  useEffect(() => {
    document.addEventListener('click', changeModalStatus);
    return () => {
      document.removeEventListener('click', changeModalStatus);
    };
  }, []);

  return (
    <>
      {viewMode!='look'&&
            <label
            className={
              readOnly
                ? 'react-fine-uploader-file-input-container react-fine-uploader-gallery-file-input-container-no-hover'
                : `react-fine-uploader-file-input-container react-fine-uploader-gallery-file-input-container ${controlId}`
            }
            style={containerStyle}
            ref={uploadBtnRef}
            onClick={handleClick}
          >
            <span
              className={
                readOnly
                  ? 'react-fine-uploader-gallery-file-input-content--disabled'
                  : 'react-fine-uploader-gallery-file-input-content'
              }
            >
              {renderContent}
            </span>
            {renderModal}
          </label>}

      <input
        ref={inputRef}
        multiple={multiple}
        className={`react-fine-uploader-file-input ${controlId}`}
        onChange={(e) => fileChange(e)}
        style={inputStyle}
        type="file"
      />
    </>
  );
});

export default UploadButton;
